﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Reflection;
using System.Collections.ObjectModel;
using System.IO;
using System.Runtime.Serialization.Formatters.Binary;
using System.Xml;
using LocalizeMe.ResourceTool.Dictionary;
using LocalizeMe.ResourceTool.VSTools;

namespace LocalizeMe.ResourceTool
{
    public partial class MainForm : Form
    {

        public MainForm()
        {
            InitializeComponent();
        }

        List<AssemblyItem> AnalyzedAssemblies = new List<AssemblyItem>();

        DataSet dsDescriptions;
        DataSet dsMessages;
        DataSet dsForms;
        DataSet dsUnbounded;

        AssemblyItem selectedItem = null;

        private string _fileLanguagesPath = @"E:\Developpement\Code Generator 2005\0.3\30 - Réalisation\Iris.GUI\Languages";
        public string FileLanguagesPath
        {
            get
            {
                return _fileLanguagesPath;
            }
            set
            {
                _fileLanguagesPath = value;
            }
        }

        private void RefreshDataGrid()
        {
            foreach (DataGridViewRow dvr in dataDescription.Rows)
            {
                if (dvr.Cells[0].Value != null &&
                    !string.IsNullOrEmpty(dvr.Cells[1].Value.ToString()) &&
                    string.IsNullOrEmpty(dvr.Cells[2].Value.ToString()))
                    dvr.Cells[1].Style.ForeColor = Color.Red;
                else
                    dvr.Cells[1].Style.ForeColor = Color.Black;

                for (int i = 2; i < dvr.Cells.Count; i++)
                {
                    if (dvr.Cells[i].Value != null && dvr.Cells[i].Value.ToString().Equals("NO FILE"))
                    {
                        dvr.Cells[i].Style.ForeColor = Color.Red;
                    }
                }
            }
        }

        private void treeView1_AfterSelect(object sender, TreeViewEventArgs e)
        {
            if (e.Node.Tag == "File")
            {
                string project = e.Node.Parent.Text;
                foreach (VSProject pr in _currentSolution.Projects)
                {
                    if (pr.Name == e.Node.Parent.Text)
                    {
                        foreach (VSItem it in pr.Items)
                        {
                            if (it.Name == e.Node.Text)
                            {
                                Analyzers.DescriptionAttributeAnalyzer ana = new LocalizeMe.ResourceTool.Analyzers.DescriptionAttributeAnalyzer(it.FilePath);
                                ana.GetDatas();
                            }
                        }
                    }
                }
            }
        }

        private DataSet LoadLanguages(DataSet ds)
        {
            DataTable t = ds.Tables[0];
            Collection<string> languages = Resource.GetAvailableCultures();
            if (languages == null)
                return ds;

            foreach (string language in languages)
            {
                DataColumn c = new DataColumn(language);
                t.Columns.Add(c);

                string filePath = Path.Combine(selectedItem.LanguagePath, language + ".lang");
                if (File.Exists(filePath))
                {
                    DataSet tmpDs = new DataSet();
                    tmpDs.ReadXml(filePath);
                    DataTable tmpT = tmpDs.Tables[0];
                    foreach (DataRow dr in tmpT.Rows)
                    {
                        //int index = t.DefaultView.Find(dr["key"]);

                        DataRow[] drs = t.Select("code='" + dr["key"].ToString() + "'");

                        if (drs!=null && drs.Length>0)
                        {
                            drs[0][language] = dr["value"];
                        }
                        else
                        {
                            //Il faut ajouter le code car on ne l'a pas trouvé !
                            DataRow dr2 = t.NewRow();
                            dr2[language] = dr["value"];
                            dr2["code"] = dr["key"];
                            t.Rows.Add(dr2);
                        }
                    }
                }
                else
                {
                    foreach (DataRow dr in t.Rows)
                    {
                        dr[language] = "NO FILE";
                    }
                }
            }
            return ds;
        }

        private DataSet LoadDataSet(AssemblyItem analysedAssembly)
        {
            DataSet ds = CreateDataSet();
            DataTable t = ds.Tables[0];
            foreach (TypeItem type in analysedAssembly.Items)
            {
                foreach (PropertyItem property in type.Properties)
                {
                    DataRow dr = t.NewRow();
                    dr["type"] = type.Name;
                    dr["property"] = property.Name;
                    dr["code"] = property.Item.Code;
                    t.Rows.Add(dr);
                }
            }

            return ds;
        }

        private DataSet CreateDataSet()
        {
            DataSet ds = new DataSet();

            DataTable t = new DataTable();

            DataColumn c= new DataColumn("type");
            t.Columns.Add(c);

            c = new DataColumn("property");
            t.Columns.Add(c);

            c = new DataColumn("code");
            t.Columns.Add(c);

            ds.Tables.Add(t);
            return ds;
        }

        private void MainForm_Load(object sender, EventArgs e)
        {
            //AssemblyItem it = AssemblyItem.AnalyseAssembly(@"E:\Developpement\Code Generator 2005\0.3\30 - Réalisation\Iris.Tools\bin\Debug\Iris.Common.dll");
            //it.SubFolder = "Common";
            //if (it != null)
            //    AnalyzedAssemblies.Add(it);


            RefreshTreeview();
        }

        private void RefreshTreeview()
        {
            treeView1.Nodes.Clear();
			TreeNode solutionNode;
			TreeNode projectNode;
            
			if (_currentSolution != null)
			{
				solutionNode = treeView1.Nodes.Add(_currentSolution.Name);
                solutionNode.ImageIndex = 0;
                solutionNode.SelectedImageIndex = 0;
                solutionNode.StateImageIndex = 0;

				foreach (VSProject project in _currentSolution.Projects)
				{
					projectNode=solutionNode.Nodes.Add(project.Name);
                    projectNode.ImageIndex = 1;
                    projectNode.SelectedImageIndex = 1;
                    projectNode.StateImageIndex = 1;

					foreach (VSItem file in project.Items)
					{
						projectNode.Nodes.Add(FillChildren(file));
					}
				}
			}
        }

        private TreeNode FillChildren(VSItem item)
        {
            if (item == null)
                return null;

            TreeNode tn = new TreeNode(item.Name);
            if (item.IsFolder)
            {
                tn.ImageIndex = 3;
                tn.SelectedImageIndex = 3;
                tn.StateImageIndex = 3;
                
            }
            else
            {
                tn.ImageIndex = 2;
                tn.SelectedImageIndex = 2;
                tn.StateImageIndex = 2;
                tn.Tag = "File";
            }
            
            
            foreach(VSItem it in item.SubItems)
            {
                tn.Nodes.Add(FillChildren(it));
            }

            return tn;
        }

        private void btnSave_Click(object sender, EventArgs e)
        {
            //TODO: changer pour la bonne boite de dialogue

            SaveFileDialog frm = new SaveFileDialog();
            frm.AddExtension = true;
            frm.DefaultExt = "xmllpf";
            frm.Filter = "XML Localizer Project Files|*.xmllpf";
            frm.InitialDirectory=Path.Combine(Application.StartupPath,@"\XmlLocalizerProjects\");

            if (frm.ShowDialog() == DialogResult.OK)
            {
                try
                {
                    this.Cursor = Cursors.WaitCursor;
                    StreamWriter f = new StreamWriter(frm.FileName);
                    BinaryFormatter b = new BinaryFormatter();
                    b.Serialize(f.BaseStream, AnalyzedAssemblies);
                    f.Close();
                }
                finally
                {
                    this.Cursor = Cursors.Default;
                }
            }

            frm.Dispose();
        }

        private void btnOpen_Click(object sender, EventArgs e)
        {
            OpenFileDialog frm = new OpenFileDialog();
            frm.Filter = "XML Localizer Project Files|*.xmllpf";
            frm.InitialDirectory = Path.Combine(Application.StartupPath, @"\XmlLocalizerProjects\");
            frm.Multiselect = false;

            if (frm.ShowDialog() == DialogResult.OK)
            {
                try
                {
                    this.Cursor = Cursors.WaitCursor;
                    
                    StreamReader f = new StreamReader(frm.FileName);
                    BinaryFormatter b = new BinaryFormatter();
                    AnalyzedAssemblies = (List<AssemblyItem>)b.Deserialize(f.BaseStream);
                    f.Close();

                    for (int i = 0; i < AnalyzedAssemblies.Count; i++)
                    {
                        AnalyzedAssemblies[i] = AssemblyItem.AnalyseAssembly(AnalyzedAssemblies[i].FilePath);
                    }
                }
                finally
                {
                    this.Cursor = Cursors.Default;
                    RefreshTreeview();
                    frm.Dispose();
                }

            }
        }

        private void btnAddAssembly_Click(object sender, EventArgs e)
        {
            OpenFileDialog frm = new OpenFileDialog();
            frm.Filter = "Assembly files|*.dll;*.exe";
            frm.Multiselect = true;

            if (frm.ShowDialog() == DialogResult.OK)
            {
                foreach (string file in frm.FileNames)
                {
                    FileInfo fi=new FileInfo(file);
                    bool bFound = false;
                    foreach (AssemblyItem item in AnalyzedAssemblies)
                    {
                        if (item.Name.Equals(fi.Name))
                        {
                            bFound = true;
                            break;
                        }
                    }
                    if (!bFound)
                    {
                        AnalyzedAssemblies.Add(AssemblyItem.AnalyseAssembly(file));
                    }
                }
            }

            RefreshTreeview();
            frm.Dispose();
            
        }


        private void setSelectedItem()
        {
            foreach (AssemblyItem it in AnalyzedAssemblies)
            {
                if (it.Name.Equals(treeView1.SelectedNode.Text))
                {
                    selectedItem = it;
                    return;
                }
            }
        }

        private void LoadItem()
        {
            DataSet ds = LoadDataSet(selectedItem);
            ds = LoadLanguages(ds);

            this.dataDescription.DataSource = ds.Tables[0];

            RefreshDataGrid();

            this.propertyGrid1.SelectedObject = selectedItem;
        }

        private void btnRefresh_Click(object sender, EventArgs e)
        {
            if (treeView1.SelectedNode != null)
            {
                setSelectedItem();
            }

            LoadItem();

        }
        private DataTable GetTranslationTable()
        {
            DataTable dt = new DataTable("items");

            DataColumn c = new DataColumn("key");
            dt.Columns.Add(c);

            c = new DataColumn("value");
            dt.Columns.Add(c);

            return dt;

        }
        private void btnSaveLanguages_Click(object sender, EventArgs e)
        {
            if (dataDescription.Columns.Count > 3)
            {
                for (int i = 3; i < dataDescription.Columns.Count; i++)
                {
                    //DataTable dt=GetTranslationTable();
                    //foreach (DataGridViewRow drv in dataGridView1.Rows)
                    //{
                    //    DataRow dr = dt.NewRow();

                    //    dr["key"] = drv.Cells[2].Value;
                    //    dr["value"] = drv.Cells[i].Value;

                    //    dt.Rows.Add(dr);
                    //}
                    string language = dataDescription.Columns[i].HeaderText;
                    
                    //dt.WriteXml(outputFile);
                    WriteTranslation(language,i);
                }
            }
            
        }

        private void WriteTranslation(string language,int index)
        {
            string outputFile = Path.Combine(selectedItem.LanguagePath, language + ".lang1");
            XmlTextWriter writer = new XmlTextWriter(outputFile,Encoding.UTF8);
            writer.WriteStartElement("items");

            foreach (DataGridViewRow drv in dataDescription.Rows)
            {
                if (drv.Cells[2].Value!=null || drv.Cells[index].Value!=null)
                {
                writer.WriteStartElement("item");
                
                
                writer.WriteAttributeString("key", drv.Cells[2].Value.ToString());
                writer.WriteAttributeString("value", drv.Cells[index].Value.ToString());
                
                writer.WriteEndElement();
                }

            }

            

            writer.WriteEndElement();

            writer.Flush();
            writer.Close();
            
        }

        private void btnEmptyFields_Click(object sender, EventArgs e)
        {
            foreach (DataGridViewRow drv in dataDescription.Rows)
            {
                if ((drv.Cells[2].Value == null || 
                    string.IsNullOrEmpty(drv.Cells[2].Value.ToString())) &&
                    drv.Cells[0].Value!=null
                    )
                {
                    string ass = selectedItem.Name;

                    int index = ass.LastIndexOf('.');
                    ass = ass.Remove(index);

                    drv.Cells[2].Value=ass + "." + drv.Cells[0].Value + ".Description." + drv.Cells[1].Value;
                }
            }
        }

		private VSSolution _currentSolution = null;

		private void btnAddSolution_Click(object sender, EventArgs e)
		{
			OpenFileDialog frm = new OpenFileDialog();
			frm.Filter = "Solution files|*.sln";
			frm.Multiselect = false;
			frm.CheckFileExists = true;

			if (frm.ShowDialog() == DialogResult.OK)
			{
				_currentSolution= VSSolution.GetVSSolution(frm.FileName);
				RefreshTreeview();
			}

			RefreshTreeview();
			frm.Dispose();
		}

        
        private void treeView1_BeforeExpand(object sender, TreeViewCancelEventArgs e)
        {
            if (e.Node.ImageIndex == 3)
            {
                e.Node.ImageIndex = 4;
                e.Node.SelectedImageIndex = 4;
            }
        }

        private void treeView1_BeforeCollapse(object sender, TreeViewCancelEventArgs e)
        {
            if (e.Node.ImageIndex == 4)
            {
                e.Node.ImageIndex = 3;
                e.Node.SelectedImageIndex = 3;
            }
        }

        

        

    }
}